package com.zhuiyun.project.api.lottery.task;

import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson2.JSON;
import com.zhuiyun.project.api.lottery.entity.Lottery;
import com.zhuiyun.project.api.lottery.service.LotteryService;
import com.zhuiyun.project.api.record.service.RecordService;
import com.zhuiyun.project.api.recording.entiy.TransactionHistory;
import com.zhuiyun.project.api.recording.model.TransactionHistoryModel;
import com.zhuiyun.project.api.recording.service.TransactionHistoryService;
import com.zhuiyun.project.api.submitrecord.entity.SubmitRecord;
import com.zhuiyun.project.api.submitrecord.service.ISubmitService;
import com.zhuiyun.project.api.sysUser.mapper.SysUserMapper;
import com.zhuiyun.project.util.ObjectUtils;
import com.zhuiyun.project.util.RedisUtil;
import com.zhuiyun.project.util.constants.CommonConstants;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.client.RestTemplate;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.List;
import java.util.Map;

/**
 * @ClassName AsyncLotteryData
 * @Description  定时任务
 * @Author 17179
 * @Date 2024/7/16 15:55
 **/
@Component
public class AsyncLotteryData {
    @Autowired
    RestTemplate restTemplate;

    @Autowired
    LotteryService lotteryService;

    @Autowired
    ISubmitService iSubmitService;
    @Autowired
    RecordService recordService;
    @Autowired
    TransactionHistoryService transactionHistoryService;
    @Autowired
    SysUserMapper sysUserMapper;
    @Value("${lottery.appCode}")
    public String appCode;
    @Value("${lottery.url}")
    public String lotteryUrl;
    @Scheduled(cron = "0 0 22,0 ? * *")
 //@Scheduled(fixedRate = 5000)
    public void asyncData(){
        try{
            // 同步排列三
            async3DAndPlw("plw");
        }catch (Exception e){
            e.printStackTrace();
        }
        try{
            // 同步福彩3d
            async3DAndPlw("fcsd");
        }catch (Exception e){
            e.printStackTrace();
        }
        try{
            // 同步所有类型数据
            asyncAllType();
        }catch (Exception e){
            e.printStackTrace();
        }

    }
    public void async(){

    }
    public void async3DAndPlw(String type){
        int count = lotteryService.selectLotteryCount(type);
        if (count < 105){ // 数据需要展示100条数据 但是数据计算需要102条 如果数据不够则下载 至少下载102条数据到数据库 这里下载150条
            for (int i=1;i<4;i++){
                try{
                    String url =  lotteryUrl+"?appCode="+appCode+"&lotteryId="+type+"&pageSize=50&page="+i;
                    String response = restTemplate.getForObject(url,String.class);
                    JSONObject map = JSONObject.parseObject(response);
                    JSONObject jsonObject = (JSONObject)map.get("data");
                    String o = jsonObject.get("lotteryResList").toString();
                    List<Lottery> list = JSON.parseArray(o, Lottery.class);
                    int is = lotteryService.saveListLottery(list);
                    if(is>0){
                        clearRecord();
                        clearJLData();
                        updateFlag();
                        separateAccounts();
                    }
                    RedisUtil.del(CommonConstants.NUM+type);
                }catch (Exception e){
                    e.printStackTrace();
                }
            }
        }else { // 否则只需同步最新10条数据即可
            String url =  lotteryUrl+"?appCode="+appCode+"&lotteryId="+type+"&pageSize=10&page=1";
            String response = restTemplate.getForObject(url,String.class);
            JSONObject map = JSONObject.parseObject(response);
            JSONObject jsonObject = (JSONObject)map.get("data");
            String o = jsonObject.get("lotteryResList").toString();
            List<Lottery> list = JSON.parseArray(o, Lottery.class);
            int i = lotteryService.saveListLottery(list);
            if(i>0){
                clearRecord();
                clearJLData();
                updateFlag();
                separateAccounts();
            }
            RedisUtil.del(CommonConstants.NUM+type);
        }

    }

    /**
     * 定时清空每天提交记录
     */
    //@Scheduled(cron = "0 0 0 ? * *")
    public void clearRecord(){
        // 清理提交数据
        recordService.clearRecord();
        // 清理个人提交数据
        recordService.clearMyRecord();
    }
    /**
     * 定时清空每天的接龙数据
     */
   // @Scheduled(cron = "0 0 22 ? * *")
   // @Scheduled(fixedRate = 5000)
    public void clearJLData(){
        RedisUtil.del("plw","fcsd");
        RedisUtil.del(CommonConstants.JL+"plw");
        RedisUtil.del(CommonConstants.JL+"fcsd");
    }



    //@Scheduled(fixedRate = 5000)
    public void asyncAllType(){
        String [] types = {"ssq","dlt","qlc","fcsd","qxc","pls","plw"};
        for (String type:types){
            String url =  lotteryUrl+"?appCode="+appCode+"&lotteryId="+type+"&pageSize=1&page=1";
            String response = restTemplate.getForObject(url,String.class);
            JSONObject map = JSONObject.parseObject(response);
            JSONObject jsonObject = (JSONObject)map.get("data");
            String o = jsonObject.get("lotteryResList").toString();
            List<Lottery> list = JSON.parseArray(o, Lottery.class);
            if(ObjectUtils.isNotEmpty(list)){
                RedisUtil.hset(CommonConstants.CPTYPES,type,list.get(0));
            }
        }
    }

    /**
     * 更新中奖状态
     */
//    @Scheduled(fixedRate = 5000)
    public void updateFlag() {
        try {
            updateWinFlag("plw");
        }catch (Exception e){
            e.printStackTrace();
        }
        try {
            updateWinFlag("fcsd");
        }catch (Exception e){
            e.printStackTrace();
        }

    }
    /**
     * 更新中奖装填
     */
    public void updateWinFlag(String type) {
        // 获取最新的奖号 和 期数
        String lastLotteryRes = lotteryService.getLastLotteryRes(type);
        String lastLotteryNo = lotteryService.getLastLotteryNo(type);
        if(ObjectUtils.isNotEmpty(lastLotteryRes)&&ObjectUtils.isNotEmpty(lastLotteryNo)){
            lastLotteryRes = lastLotteryRes.replace(",","").substring(0,3);
            List<SubmitRecord> list = iSubmitService.getLastSubmit(type,lastLotteryNo);
            for (SubmitRecord submitRecord:list){
                String result = submitRecord.getResult();
                if(ObjectUtils.isNotEmpty(result)){
                    if(result.indexOf(lastLotteryRes)!=-1){
                        submitRecord.setFlag(1);
                        iSubmitService.updateSubmitFlag(submitRecord);
                    }
                }
            }
        }

    }

    /**
     * 每天10点开奖后进行分账
     */
   // @Scheduled(fixedRate = 5000)
    public void separateAccounts(){
        // 排三和福彩3d期号都是一样的
        String lastLotteryNo = lotteryService.getLastLotteryNo("plw");
        // 查询出中奖且不免费并且有人付费的项目进行分账
        List<TransactionHistoryModel> submitRecordByCountAndStatusAndFlag = transactionHistoryService.getSubmitRecordByCountAndStatusAndFlag(lastLotteryNo);
        for(TransactionHistoryModel transactionHistoryModel:submitRecordByCountAndStatusAndFlag){
            Integer flag = transactionHistoryModel.getFlag();
            BigDecimal originalPrice = transactionHistoryModel.getAmount();
            if(flag == 1){ // 中奖的需要平台和产品发布者分配金币
                // 1. 扣除平台获得一个产品的金币  然后分账比例之后分账到 平台和发布者的账户 按照4 6 分配比例
                BigDecimal discountRate = new BigDecimal("0.4"); // 打6折
                // 计算折后价格  这是用户需要的金额
                BigDecimal discountedPrice = originalPrice.multiply(discountRate).setScale(2, RoundingMode.HALF_UP);
                try{
                    // 更新用户金币需要加锁
                    updateAmount(transactionHistoryModel.getPhoneNumber(),discountedPrice,transactionHistoryModel.getId(),CommonConstants.SEPARATE);

                }catch (Exception e){

                }
            }else{ // 不中奖全部返回给用户
                try{
                    // 不中返还
                    updateAmount(transactionHistoryModel.getRechargeUserPhone(),originalPrice,transactionHistoryModel.getId(),CommonConstants.REFUND);
                }catch (Exception e){

                }
            }
        }
    }

    /**
     * 中奖分账
     * @param phone
     * @param discountedPrice
     */
    @Transactional
    public void updateAmount(String phone,BigDecimal discountedPrice,Integer id,String state){
        int rowsAffected = sysUserMapper.updateAmountByPhone(phone, discountedPrice);
        // admin用户扣款
        int i1 = sysUserMapper.updateAdminAmount(1, discountedPrice.negate());
        transactionHistoryService.updateSeparateFlag(id,state);
    }
}
